/**
 * @file    main.c 
 * @author  18408107475@163.com
 * @version V1.0.0
 * @date    2025-07-15
 * @brief   基于MPU6050的六轴传感器数据采集与显示系统
 * @details 
 * 硬件配置：
 *   - 主控芯片：STM32F10x系列（如STM32F103C8T6，64KB Flash，20KB RAM）
 *   - 传感器：MPU6050（三轴加速度计+三轴陀螺仪，I2C接口）
 *   - 显示设备：OLED SSD1315（128x64分辨率，I2C接口，支持16级灰度）
 *   - 硬件连接：
 *     - MPU6050 SCL → PB6（需4.7K上拉电阻到3.3V，支持开漏输出）
 *     - MPU6050 SDA → PB7（需4.7K上拉电阻到3.3V）
 *     - MPU6050 AD0 → GND（I2C地址0x68，若接VCC则地址为0x69）
 *     - OLED与MPU6050共用I2C总线（地址不同，通过I2C仲裁机制区分）
 * 
 * 软件特性：
 *   - 传感器配置：MPU6050初始化参数：
 *     - 加速度计量程：±16g（灵敏度2048 LSB/g）
 *     - 陀螺仪量程：±2000°/s（灵敏度16.4 LSB/(°/s)）
 *     - 采样率：100Hz（由SMPLRT_DIV=9配置）
 *     - 低通滤波器：5Hz（滤除高频噪声，适合静态姿态检测）
 *   - 数据处理：
 *     - 原始数据采集（未做校准和滤波）
 *     - 实时显示（刷新率约100Hz，受I2C通信速度限制）
 *   - 显示布局：
 *     - 第0行：设备ID（验证通信）
 *     - 左半屏：加速度计数据（AX/AY/AZ）
 *     - 右半屏：陀螺仪数据（GX/GY/GZ）
 */

/* Includes ------------------------------------------------------------------*/
#include "stm32f10x.h"              // STM32标准外设库（提供片上外设寄存器定义和操作函数）
#include "Delay.h"                  // 延时函数库（基于SysTick实现，用于初始化阶段时序控制）
#include "USART1_Config.h"          // USART1配置（备用调试接口，波特率115200，未实际使用）
#include "OLED_SSD1315_Config.h"    // OLED驱动库（I2C通信、显存操作、字体渲染）
#include "MPU6050_Config.h"         // MPU6050传感器驱动（I2C通信、寄存器配置、数据采集）


/* 私有变量定义 --------------------------------------------------------------*/
u8 ID;                               // 存储MPU6050的设备ID（WHO_AM_I寄存器值，正常为0x68）
int16_t AX, AY, AZ;                  // 加速度计X/Y/Z轴原始数据（16位有符号整数，范围-32768~32767）
int16_t GX, GY, GZ;                  // 陀螺仪X/Y/Z轴原始数据（16位有符号整数，反映角速度）


/**
 * @brief  主程序入口
 * @param  None
 * @retval int 程序状态码（实际不返回，因主循环为无限循环）
 * @执行流程：
 *   1. 系统初始化：
 *      - 初始化MPU6050传感器（配置工作模式、量程、采样率）
 *      - 初始化OLED显示屏（I2C通信、显存初始化）
 *      - 读取并显示MPU6050设备ID（验证硬件连接）
 *   2. 数据采集与显示循环：
 *      - 持续读取六轴原始数据（加速度计+陀螺仪）
 *      - 在OLED分区域显示各轴数据
 *      - 无延时循环（刷新率取决于I2C通信速度，约100Hz）
 * @注意事项：
 *   - 未使用操作系统，采用裸机编程模型（单线程顺序执行）
 *   - 主循环无延时，CPU利用率高，适合实时性要求高的应用
 */
int main(void)
{
    // 初始化MPU6050传感器：
    // 1. 解除休眠状态（PWR_MGMT_1寄存器）
    // 2. 选择陀螺仪X轴作为时钟源（提高稳定性）
    // 3. 配置采样率为100Hz（SMPLRT_DIV=9 → 1kHz/(9+1)）
    // 4. 设置低通滤波器带宽为5Hz（CONFIG=0x06）
    // 5. 配置加速度计量程±16g（ACCEL_CONFIG=0x18）
    // 6. 配置陀螺仪量程±2000°/s（GYRO_CONFIG=0x18）
    MPU6050_Config();

    // 初始化OLED显示屏：
    // 1. 配置I2C总线（复用开漏模式，100kHz）
    // 2. 发送SSD1315初始化命令序列（复位、设置对比度、扫描方向等）
    // 3. 清屏并初始化显存
    OLED_SSD1315_Config();       

    // 清屏操作：
    // - 向SSD1315发送显存写入命令
    // - 将整个显存（128x64位）置为0（黑屏状态）
    OLED_SSD1315_Clear();       
    
    // 在OLED第0行（顶部）显示固定文本"ID: "：
    // - 字体大小：16x16像素（占用2行8x8像素空间）
    // - 左对齐显示
    // - 实际显示位置：第0行，第0列（左上角）
    OLED_SSD1315_ShowString(0, 0, "ID: ", 16, false);
    
    // 读取MPU6050的设备ID：
    // - 读取WHO_AM_I寄存器（地址0x75）
    // - 正常值为0x68（与AD0引脚状态无关）
    ID = MPU6050_GetID();
    
    // 在"ID: "文本后显示设备ID值：
    // - 显示位置：第0行，第25列（字符宽度计算得出）
    // - 显示格式：4位数字（不足补零，如"0068"）
    // - 字体大小：16x16像素
    OLED_SSD1315_ShowNum(25, 0, ID, 4, 16);

    // 无限循环：持续采集并显示数据
    while (1)                   
    {
        // 读取六轴原始数据：
        // - 加速度计数据范围：±32767（对应±16g物理量程）
        //   例如：AX=2048 → 实际加速度=2048/2048=1g
        // - 陀螺仪数据范围：±32767（对应±2000°/s物理量程）
        //   例如：GX=16400 → 实际角速度=16400/16.4=1000°/s
        MPU6050_GetData(&AX, &AY, &AZ, &GX, &GY, &GZ);
        
        // 在OLED显示加速度计数据（左半屏，第2、4、6行）：
        // - 显示格式："AX: xxxxx"（5位数字，包含符号）
        // - 字体大小：8x8像素（每行可显示16个字符）
        // - 第2行：X轴加速度
        // - 第4行：Y轴加速度
        // - 第6行：Z轴加速度
        OLED_SSD1315_ShowString(0, 2, "AX:", 8, false);  // 第2行显示"AX:"标签
        OLED_SSD1315_ShowNum(17,  2, AX, 6, 8);           // 第2行显示AX值（6位宽度含符号）
        
        OLED_SSD1315_ShowString(0, 4, "AY:", 8, false);  // 第4行显示"AY:"标签
        OLED_SSD1315_ShowNum(17,  4, AY, 6, 8);           // 第4行显示AY值
        
        OLED_SSD1315_ShowString(0, 6, "AZ:", 8, false);  // 第6行显示"AZ:"标签
        OLED_SSD1315_ShowNum(17,  6, AZ, 6, 8);           // 第6行显示AZ值
        
        // 在OLED显示陀螺仪数据（右半屏，第2、4、6行）：
        // - 显示格式："GX: xxxxx"（5位数字，包含符号）
        // - 字体大小：8x8像素
        // - 第2行：X轴角速度
        // - 第4行：Y轴角速度
        // - 第6行：Z轴角速度
        OLED_SSD1315_ShowString(66, 2, "GX:", 8, false); // 第2行显示"GX:"标签
        OLED_SSD1315_ShowNum(83, 2, GX, 6, 8);           // 第2行显示GX值
        
        OLED_SSD1315_ShowString(66, 4, "GY:", 8, false); // 第4行显示"GY:"标签
        OLED_SSD1315_ShowNum(83, 4, GY, 6, 8);           // 第4行显示GY值
        
        OLED_SSD1315_ShowString(66, 6, "GZ:", 8, false); // 第6行显示"GZ:"标签
        OLED_SSD1315_ShowNum(83, 6, GZ, 6, 8);           // 第6行显示GZ值
        
        // 循环无延时，刷新频率取决于I2C通信速度（约100Hz）
        // 每次循环完成一次完整的数据采集和显示
    }
}

/************************ (C) COPYRIGHT 2025 TS *****END OF FILE****/
